<template>
  <!--
  @name: HyTable
  @data: 2024/7/3 9:33
-->
  <div id="hy-table">
    <!--   判断是否在表头显示按钮  -->
    <!--  使用externalBtnList方式  -->
    <el-row :gutter="3.5" v-if="elTableConfig.externalBtnList?.length>0">
      <el-col v-for="btnObject of elTableConfig.externalBtnList" span="24">
        <el-button
          v-if="btnObject.showCallback?btnObject.showCallback(multipleSelection):true"
          :type="btnObject.type?btnObject.type:'primary'"
          :size="btnObject.size?btnObject.size:'small'"
          :plain="btnObject.plain"
          :round="btnObject.round"
          :circle="btnObject.circle"
          :text="btnObject.text"
          @click="btnCallback(scope?scope.row:null, btnObject.isUpdateTableData, btnObject.clickCallback)"
          :disabled="btnObject.disableCallback?btnObject.disableCallback(multipleSelection):false"
        >
          {{btnObject.label}}
        </el-button>
      </el-col>
    </el-row>
    <!--  使用operating方式  -->
    <el-row :gutter="3.5" v-else-if="elTableConfig.btnPosition==='external' && elTableConfig.operating.length>=0">
      <el-col v-for="btnObject of elTableConfig.operating" span="24">
        <el-button
          v-if="btnObject.showCallback?btnObject.showCallback(multipleSelection):true"
          :type="btnObject.type?btnObject.type:'primary'"
          :size="btnObject.size?btnObject.size:'small'"
          :plain="btnObject.plain"
          :round="btnObject.round"
          :circle="btnObject.circle"
          :text="btnObject.text"
          @click="btnCallback(scope?scope.row:null, btnObject.isUpdateTableData, btnObject.clickCallback)"
          :disabled="btnObject.disableCallback?btnObject.disableCallback(multipleSelection):false"
        >
          {{btnObject.label}}
        </el-button>
      </el-col>
    </el-row>

    <!--  表格主体  -->
    <el-table
      ref="hyTableRef"
      :data="tableData"
      style="width: 100%"
      @selection-change="handleSelectionChange"
      @row-click="rowClick"
    >
      <el-table-column v-if="elTableConfig.selection" type="selection" width="55" />
      <el-table-column v-for="(item,index) of elTableConfig.column"
                       :prop="item.prop"
                       :label="item.label"
                       :width="item.width?item.width:''"
                       :key="item.prop"
                       :show-overflow-tooltip="item.showOverflowTooltip"
      >
        <template v-if="item.columnShowCallback" #default="scope">
            <div v-html="item.columnShowCallback(scope.row)"></div>
        </template>

      </el-table-column>

      <!--   判断是否在表格内部显示,这里的文字我们直接就写成操作了,后期场景不够时在进行修改   -->
      <el-table-column label="操作" v-if="elTableConfig.internalBtnList?.length>0">
        <template #default="scope">
          <template v-for="btnObject of elTableConfig.internalBtnList">
            <el-button
              v-if="btnObject.showCallback?btnObject.showCallback(scope?scope.row:multipleSelection):true"
              :type="btnObject.type?btnObject.type:'primary'"
              :size="btnObject.size?btnObject.size:'small'"
              :plain="btnObject.plain"
              :round="btnObject.round"
              :circle="btnObject.circle"
              :text="btnObject.text"
              @click="btnCallback(scope.row,btnObject.isUpdateTableData,btnObject.clickCallback)"
              :disabled="btnObject.disableCallback?btnObject.disableCallback(scope?scope.row:multipleSelection):false"
            >
              {{btnObject.label}}
            </el-button>
          </template>
        </template>
      </el-table-column>
      <el-table-column label="操作" v-else-if="elTableConfig.btnPosition==='internal' && elTableConfig.operating?.length>0">
        <template #default="scope">
          <template v-for="btnObject of elTableConfig.operating">
            <el-button
              v-if="btnObject.showCallback?btnObject.showCallback(scope?scope.row:multipleSelection):true"
              :type="btnObject.type?btnObject.type:'primary'"
              :size="btnObject.size?btnObject.size:'small'"
              :plain="btnObject.plain"
              :round="btnObject.round"
              :circle="btnObject.circle"
              :text="btnObject.text"
              @click="btnCallback(scope.row,btnObject.isUpdateTableData,btnObject.clickCallback)"
              :disabled="btnObject.disableCallback?btnObject.disableCallback(scope?scope.row:multipleSelection):false"
            >
              {{btnObject.label}}
            </el-button>
          </template>
        </template>
      </el-table-column>
    </el-table>

    <!--分页器-->
    <el-pagination
      class="hy-el-pagination"
      :total="total"
      :background="elTableConfig.paginationConfig?.background"
      :current-page="paginationData.pageNum"
      :page-size="paginationData.pageSize"
      :layout="elTableConfig.paginationConfig.layout?elTableConfig.paginationConfig.layout:'prev, pager, next, sizes'"
      @current-change="currentChangePageNum"
      @size-change="sizeChange"
    />

  </div>
</template>
<script setup lang="ts">
import {computed, reactive, ref} from "vue";
import type HyTableInterface from "@/interface/HyTableInterface";
import {hyElementRequest} from "@/components/utils";
import { ElTable } from 'element-plus'
import {deleteUserApi, selectUserByIdApi} from "@/api/user";
/** 表格的虚拟dom对象 */
const hyTableRef=ref<InstanceType<typeof ElTable>>();

/**
 * 分页器数据类型，无需导出，只在本页面使用
 */
type paginationDataType={
  pageSize?:number,
  pageNum?:number,
  total?:number
}


/** 被选中的表格数据,
 * 这里的数组长度为1
 * 是因为当单选时,我们返回最近单击一次的那一行数据 */
const multipleSelection = ref<any>(Array(1));

// const elTableConfig=reactive<HyTableInterface>(
//   {
//     url:"user/page",
//     btnPosition:"internal",
//     isSelectionByRow: true,
//     selection: true,
//     operating:[
//       {
//         operationType:"custom",
//         label:"查看",
//         clickCallback:function (rows) {
//         },
//         size:"large",
//         disableCallback:(rows)=>{
//           if (rows.userId===1){
//             return true;
//           }
//           return false;
//         },
//       },
//       {
//         operationType:"custom",
//         label:"删除",
//         isUpdateTableData: true,
//         // clickCallback: async function (rows) {
//         //   // console.log(101, rows);
//         //   //这里我们使用删除接口,进行测试
//         //  // const result=await deleteUserApi(rows.userId);
//         // },
//         size:"large"
//       }
//     ],
//     column:[
//       {
//         prop:"cover",
//         label:"用户头像",
//         columnShowCallback:function (rows, index) {
//           return `<img style="width: 100px;height: 100px;" src="${rows.cover}"/>`;
//         }
//       },
//       {
//         prop:"phone",
//         label:"电话号码",
//       },
//       {
//         prop:"nickname",
//         label:"用户昵称",
//       },
//       {
//         prop: "realname",
//         label: "用户真实姓名",
//       },
//       {
//         prop:"birthday",
//         label:"用户生日",
//       },
//       {
//         prop:"introduction",
//         label:"用户介绍",
//         showOverflowTooltip:true,
//       },
//     ],
//     isShowPagination:true,
//     paginationConfig:{
//       background: true,
//     }
//   }
// );


const elTableConfig=defineProps<HyTableInterface>();

/** 双向绑定 */
const form = defineModel("form", {
  type: Object,
  default: () => {
  },
});
const total=ref<number>(0);
/** 分页器参数 */
const paginationData=reactive<paginationDataType>({
  pageSize:elTableConfig.paginationConfig?.pageSize?elTableConfig.paginationConfig.pageSize:10,
  pageNum:1,
});

/**
 * @description 当前页改变时触发
 * @param value 页面改变后的值
 */
function currentChangePageNum(value: number){
  paginationData.pageNum=value;
  console.log(185, paginationData);
  init();
}

/**
 * @description 页数改变时触发
 * @param value 页面改变后的值
 */
function sizeChange(value: number) {
  paginationData.pageSize=value;
  init();
}

/**
 * @description 回调,执行操作等
 * @param currentRow 当前单击的数据
 * @param isUpdateTableData 是否更新表格
 * @param itemCallback 当前json配置的按钮回调函数
 */
function btnCallback(currentRow:object | null, isUpdateTableData?:boolean, itemCallback?:Function) {
  //回调函数是否存在
  if (itemCallback){
    //判断是否需要更新表格
    if (isUpdateTableData){
      //判断itemCallback是否异步函数
      if (Object.prototype.toString.call(itemCallback) === '[object AsyncFunction]'){
        //如果为多选状态,则返回数组
        if (elTableConfig.selection){
          itemCallback(multipleSelection.value).then((result:any)=>{
            init();
          },(error:any)=>{
            console.log(error);
          });
        }else{
          //单选时,返回当前对象
          itemCallback(currentRow).then((result:any)=>{
            init();
          },(error:any)=>{
            console.log(error);
          });
        }
      }else{
        console.error("isUpdateTableData开启时,clickCallback需要是异步函数");
      }
    }else{
      //未开启更新表格数据
      if (elTableConfig.selection){
        itemCallback(multipleSelection.value);
      }else {
        itemCallback(currentRow);
      }
    }
  }
}

/** 当复选框状态改变时触发 */
const handleSelectionChange = (val: any) => {
  console.log(249, val);
  multipleSelection.value=val;
}

/** 单击一行的回调 */
const rowClick=(row: any, column: any, event: Event)=>{
  console.log(255, row);
  /** 时候开启单击一行选中 */
  if (elTableConfig.isSelectionByRow){//启动多选
    // @ts-ignore
    hyTableRef.value!.toggleRowSelection(row,undefined);
  }
}



/** 表格数据 */
const tableData=ref(elTableConfig.data);
init();

/**
 * @description 初始化方法
 */
function init() {
  /** 重新定义数据，发送请求 */
  const requestBody={...form.value,...paginationData};
  console.log(272, requestBody);
  if (elTableConfig.url){
    //开始发送请求
    hyElementRequest(
      elTableConfig.method,
      elTableConfig.url,
      // elTableConfig.data,
      // elTableConfig.params,
      requestBody,
      requestBody,
      elTableConfig.requestCallback,
      elTableConfig.responseCallback
    ).then((result:any)=>{
      if (result.code===200){
        tableData.value=result.data.data;
        total.value=result.data.total;
      }
    },(error)=>{
      console.log(error);
    });
  }
}

</script>
<style scoped>
.user_cover{
  width: 150px;
  height: 150px;
}
.hy-el-pagination{
  margin: 10px auto;
  width: max-content;
}
@media screen(1200px)  {
  .hy-el-pagination{
    display: none;
  }
}
</style>
